#include "base/timeevent.h"
#include "base/timebplustree.h"
#include "base/log.h"
namespace net_tools::base
{
  // (2,1,true) return true
  // (2,2,true) return true
  // (2,2,false) return false
  bool compare_func(timeval ltime, timeval rtime, bool is_same_return_true)
  {
    return (ltime.tv_sec > rtime.tv_sec) ||
           ((ltime.tv_sec == rtime.tv_sec) &&
            ((ltime.tv_usec > rtime.tv_usec) ||
             ((ltime.tv_usec == rtime.tv_usec) && is_same_return_true)));
  };
  Timebplustree::Timebplustree()
      : bplustree_(compare_func){};
  void Timebplustree::Insert_timeevent(Timeevent *p_timeevent)
  {
    bplustree_.Insertdata(p_timeevent, p_timeevent->next_time_, bplustree_.root_);
  };
  void Timebplustree::Dotimeevent()
  {
    timeval now_time_;
    gettimeofday(&now_time_, NULL);
    auto [key_leaf_, key_in_leaf_index_] = bplustree_.Find_leaf(now_time_);
    if (key_in_leaf_index_ == -1)
    {
      bplustree_.Del_loop();
      return;
    }
    util::Bplustreeleaf<Timeevent *, timeval> *begin_leaf_ = bplustree_.Get_min_leaf();
    for (; begin_leaf_ != key_leaf_; begin_leaf_ = reinterpret_cast<util::Bplustreeleaf<Timeevent *, timeval> *>(begin_leaf_->next_))
    {
      int size = begin_leaf_->size_;
      for (int count = 0; count < size; ++count)
      {
        if (begin_leaf_->ptr_[count]->func_)
        {
          begin_leaf_->ptr_[count]->func_();
        }
      }
    }
    for (int count = 0; count <= key_in_leaf_index_; ++count)
    {
      if (begin_leaf_->ptr_[count]->func_)
      {
        begin_leaf_->ptr_[count]->func_();
      }
    }
    bplustree_.Del_loop();
  };
  timeval Timebplustree::Get_min_time()
  {
    return bplustree_.Get_cache_min_key();
  };
  bool Timebplustree::Is_empty()
  {
    return bplustree_.Is_empty_and_cache();
  };

} // namespace net_tools::base